<template>
  <div v-if="localComments.length > 0">
    <!-- 评论列表渲染 -->
    <div
      class="comments-o"
      :class="[cNum > 0 ? 'sub-comment' : 'main-comment']"
      v-for="(item, index) in currentPageComments"
      :key="item.id"
    >
      <!-- 用户信息展示 -->
      <div class="c-title">
        <router-link :to="goUrl + item.userId"
          ><el-avatar
            size="small"
            :src="item.userImage || defaultImage"
          ></el-avatar
        ></router-link>
        <b>{{ item.username }}</b>

        <!-- 回复目标用户展示 -->
        <span v-if="item.parentId !== 0">
          回复:@<a>{{ item.parentUserName }}</a>
        </span>

        <em>|</em>
        <!-- 时间格式化展示 -->
        <time>{{ item.createTime | dateFormat }}</time>
      </div>

      <!-- 评论内容展示 -->
      <div class="c-c highlight-tip">
        {{ item.content }}
      </div>

      <!-- 操作按钮组（含图标） -->
      <div class="c-g">
        <span @click="toggleReply(item)">
          <el-icon name="edit" class="icon-btn"></el-icon>
          回复
        </span>

        <!-- 删除按钮 -->
        <span
          @click="deleteComment(item.id)"
          v-if="item.userId === userId || userType === 'admin'"
        >
          <el-icon class="icon-btn el-icon-delete-solid" :size="16">
            <delete />
          </el-icon>
        </span>

        <!-- 点赞按钮 -->
        <span @click="likeComment(item)">
          <div class="icon-btn">
            <i class="iconfont icon-dianzan" v-if="!item.isLiked"></i>
            <i class="iconfont icon-dianzan1" v-else></i>
          </div>
          {{ item.likes }}
        </span>
      </div>

      <!-- 回复表单与子评论 -->
      <div class="lou">
        <!-- 回复表单 -->
        <el-form
          ref="replyForms"
          :model="ruleform"
          :rules="rules"
          label-width="100px"
          class="reply-form"
          v-show="item.ishf"
        >
          <el-form-item label="回复内容" prop="content">
            <el-input
              type="textarea"
              :rows="3"
              v-model="ruleform.content"
              placeholder="请输入回复内容"
              ref="replyInput"
            ></el-input>
          </el-form-item>
          <el-form-item class="plbotton">
            <el-button size="mini" type="primary" @click="submitReply(item)"
              >发送</el-button
            >
            <el-button size="mini" @click="cancelReply(item)">取消</el-button>
            <el-button size="mini" @click="resetForm(index)">重置</el-button>
          </el-form-item>
        </el-form>

        <!-- 子评论递归渲染 -->
        <comment
          v-if="item.children && item.children.length > 0"
          :comments="item.children"
          :cNum="cNum + 1"
          :competitionId="competitionId"
          :goUrl="goUrl"
          @comment-updated="$emit('comment-updated')"
        />
      </div>
    </div>

    <!-- 分页组件 -->
    <div class="pagination-container" v-if="showPagination">
      <el-pagination
        layout="prev, pager, next"
        :page-size="pageSize"
        :total="localComments.length"
        :current-page.sync="currentPage"
        @current-change="handlePageChange"
      >
      </el-pagination>
    </div>
    <div class="empty-comments" v-else-if="comments.length === 0">
      <el-empty description="暂无评论"></el-empty>
    </div>
  </div>
</template>

<script>
import {
  reqAddCompetitionComment,
  reqAddCommentLike,
  reqDeleteComment,
} from "@/api";
import "../../assets/css/iconfont.css";

// 注册自身组件（Vue2递归组件必需）
export default {
  name: "comment",
  components: {
    comment: () => import("./comment"), // 递归组件需要动态导入
  },
  props: {
    comments: {
      type: Array,
      required: true,
    },
    cNum: {
      type: Number,
      default: 0,
    },
    competitionId: {
      type: String,
      required: true,
    },
    goUrl: {
      type: String,
      required: true,
    },
  },
  data() {
    return {
      // 分页配置
      currentPage: 1,
      pageSize: 5,
      // 回复表单数据
      ruleform: {
        content: "",
      },
      localComments: [],
      // 当前活动的回复框索引（用于防抖）
      activeReplyIndex: -1,
      // 表单验证规则
      rules: {
        content: [
          { required: true, message: "请输入回复内容", trigger: "blur" },
          {
            min: 2,
            max: 500,
            message: "内容长度在2到500个字符",
            trigger: "blur",
          },
        ],
      },
      // 默认头像
      defaultImage:
        "https://cube.elemecdn.com/3/7c/3ea6beec64369c2642b92c6726f1epng.png",
    };
  },
  computed: {
    userId() {
      return this.$store.state.user.userForm.userId;
    },
    userType() {
      return this.$store.state.user.userForm.userType;
    },
    // 当前页评论数据
    currentPageComments() {
      const start = (this.currentPage - 1) * this.pageSize;
      const end = start + this.pageSize;
      return this.localComments.slice(start, end);
    },
    // 是否显示分页组件
    showPagination() {
      return this.cNum === 0 && this.localComments.length > this.pageSize;
    },
    // 总页数
    totalPages() {
      return Math.ceil(this.localComments.length / this.pageSize);
    },
  },
  watch: {
    // 监听父组件传递的 comments 变化
    comments: {
      immediate: true,
      deep: true,
      handler(newValue) {
        this.localComments = JSON.parse(JSON.stringify(newValue));
        this.currentPage = 1;
      },
    },
  },
  mounted() {
    // 添加全局点击事件监听，用于点击外部关闭回复框
    document.addEventListener("click", this.handleClickOutside);
  },
  beforeDestroy() {
    // 移除事件监听
    document.removeEventListener("click", this.handleClickOutside);
  },
  filters: {
    // 时间格式化过滤器
    dateFormat(time) {
      const date = new Date(time);
      return `${date.getFullYear()}-${String(date.getMonth() + 1).padStart(
        2,
        "0"
      )}-${String(date.getDate()).padStart(2, "0")}`;
    },
  },
  methods: {
    /**
     * 处理点击外部区域
     */
    handleClickOutside(event) {
      // 如果点击的不是回复表单区域，关闭所有回复框
      const isReplyForm = event.target.closest(".reply-form");
      const isReplyButton = event.target.closest(".c-g span");
      if (!isReplyForm && !isReplyButton) {
        this.closeAllReplyForms();
      }
    },
    /**
     * 关闭所有回复表单
     */
    closeAllReplyForms() {
      this.localComments.forEach((comment) => {
        if (comment.ishf) {
          this.$set(comment, "ishf", false);
        }
      });
      this.activeReplyIndex = -1;
    },
    /**
     * 切换回复面板
     * @param {Object} comment 当前评论对象
     */
    toggleReply(comment) {
      // 先关闭其他所有回复框
      this.closeAllReplyForms();
      // 强制设置响应式属性
      this.$set(comment, "ishf", !comment.ishf);
      // 初始化回复状态
      if (comment.ishf) {
        const index = this.currentPageComments.findIndex(
          (item) => item.id === comment.id
        );
        this.activeReplyIndex = index;
        // 聚焦到输入框
        this.$nextTick(() => {
          const input = this.$refs.replyInput && this.$refs.replyInput[index];
          if (input && input.focus) {
            input.focus();
          }
        });
      } else {
        this.activeReplyIndex = -1;
      }
    },
    /**
     * 处理输入框失去焦点
     */
    // handleInputBlur(comment, index) {
    //   // 使用 setTimeout 避免在点击取消按钮时立即关闭
    //   setTimeout(() => {
    //     // 只有当失去焦点的输入框是当前活动的回复框时才关闭
    //     if (this.activeReplyIndex === index && comment.ishf) {
    //       // 检查是否有内容，如果有内容则不自动关闭
    //       if (!this.ruleform.content.trim()) {
    //         this.cancelReply(comment);
    //       }
    //     }
    //   }, 200);
    // },
    /**
     * 取消回复
     */
    cancelReply(comment) {
      this.$set(comment, "ishf", false);
      this.activeReplyIndex = -1;
      this.ruleform.content = "";
    },

    /**
     * 提交回复
     * @param {Object} parentComment 父评论对象
     */
    async submitReply(parentComment) {
      try {
        const token =
          sessionStorage.getItem("token") ||
          this.$store.state.user?.token ||
          localStorage.getItem("token");
        if (!token || token === "null" || token === "undefined") {
          this.$message.error("请先登录后再进行回复");
          this.$router.push("/login");
          return;
        }

        // 获取对应表单索引
        const index = this.currentPageComments.findIndex(
          (item) => item.id === parentComment.id
        );

        // 表单验证
        const valid = await this.$refs.replyForms[index].validate();
        if (!valid) return;

        const newComment = {
          userId: this.userId,
          parentId: parentComment.id,
          content: this.ruleform.content,
        };

        // 添加加载状态
        const loading = this.$loading({
          lock: true,
          text: "正在提交...",
          spinner: "el-icon-loading",
          background: "rgba(0, 0, 0, 0.7)",
        });

        try {
          const res = await reqAddCompetitionComment(
            this.competitionId,
            newComment
          );

          if (res.code === 200) {
            // 更新评论数据（需根据实际接口返回处理）
            this.$message.success("回复成功");
            this.resetForm(index);
            this.$set(parentComment, "ishf", false);
            // console.log(res.data);
            // 触发父组件刷新评论列表
            this.$emit("comment-updated");
          } else {
            this.$message.error(res.msg || "回复失败");
          }
        } finally {
          loading.close();
        }
      } catch (error) {
        this.$message.error("提交失败");
        if (error.response && error.response.status === 401) {
          this.$message.error("登录过期，请重新登录");
          sessionStorage.removeItem("token");
          this.$router.push("/login");
        } else {
          this.$message.error("回复失败，请检查网络连接或稍后重试");
        }
      }
    },

    /**
     * 重置表单
     * @param {Number} index 表单索引
     */
    resetForm(index) {
      this.$refs.replyForms[index].resetFields();
    },

    /**
     * 删除评论
     * @param {Number} commentId 评论ID
     */
    async deleteComment(commentId) {
      this.$confirm("确定删除此评论吗？", "提示", {
        confirmButtonText: "确定",
        cancelButtonText: "取消",
        type: "warning",
      })
        .then(async () => {
          // 实际项目中应调用API
          try {
            const res = await reqDeleteComment(this.competitionId, commentId);
            if (res.code === 200) {
              this.$message.success("删除成功");
              //从本地评论中删除
              const deleteFormComments = (comments) => {
                const index = comments.findIndex(
                  (item) => item.id === commentId
                );
                if (index > -1) {
                  this.comments.splice(index, 1);
                  return true;
                }

                // 递归查找子评论
                for (let comment of comments) {
                  if (comment.children && comment.children.length > 0) {
                    if (deleteFormComments(comment.children)) {
                      return true;
                    }
                  }
                }
                return false;
              };
              deleteFormComments(this.localComments);

              // 如果删除后当前页没有数据且不是第一页，跳转到上一页
              if (
                this.currentPageComments.length === 0 &&
                this.currentPage > 1
              ) {
                this.currentPage--;
              }

              //通知父组件
              this.$emit("comment-updated");
            } else {
              this.$message.error(res.msg || "删除失败");
            }
          } catch (error) {
            console.error("删除评论失败：", error);
            this.$message.error("删除失败，请检查网络连接或稍后重试");
          }
        })
        .catch(() => {
          // 取消操作
        });
    },

    /**
     * 点赞评论
     * @param {Object} comment 当前评论对象
     */
    async likeComment(comment) {
      try {
        const res = await reqAddCommentLike(this.competitionId, comment.id);

        if (res.code === 200) {
          // 更新点赞状态
          this.$set(comment, "likes", res.data.likes);
          this.$set(comment, "isLiked", res.data.isLiked);
        } else {
          this.$message.error(res.msg || "点赞失败");
        }
      } catch (error) {
        this.$message.error("点赞请求失败");
        console.error("点赞接口错误：", error);
      }
    },

    /**
     * 分页处理
     * @param {Number} page 当前页码
     */
    handlePageChange(page) {
      this.currentPage = page;
      // 如果需要分页加载，可以在这里触发父组件事件或调用API****************
      this.$nextTick(() => {
        const commentSection = this.$el.querySelector(".comments-o");
        if (commentSection) {
          commentSection.scrollIntoView({ behavior: "smooth", block: "start" });
        }
      });
    },
    /**
     * 跳转到指定页
     */
    // goToPage(page) {
    //   if (page >= 1 && page <= this.totalPages) {
    //     this.currentPage = page;
    //   }
    // },

    /**
     * 更新每页显示数量
     */
    // updatePageSize(size) {
    //   this.pageSize = size;
    //   this.currentPage = 1; // 重置到第一页
    // }
  },
};
</script>

<style lang="scss" scoped>
// ====================== 变量定义（可选，提升可维护性） ======================
$primary-color: #409eff; // 主题色
$hover-color: #337ecc; //  hover 色
$border-color: #e4e7ed; // 边框色
$bg-light: #f9fafc; // 浅背景
$bg-white: #ffffff; // 白色背景
$text-dark: #303133; // 深文字色
$text-gray: #909399; // 浅文字色
$border-dashed: #ebeef5; // 虚线边框色

// ====================== 评论容器基础样式 ======================
.comments-o {
  border: 1px solid $border-color;
  border-radius: 8px;
  padding: 16px;
  margin-bottom: 16px;
  background-color: $bg-light;
  transition: all 0.3s ease;

  //  hover 阴影
  &:hover {
    box-shadow: 0 2px 12px 0 rgba(0, 0, 0, 0.05);
  }

  // 主评论 vs 子评论 样式区分
  &.main-comment {
    margin-left: 0;
  }
  &.sub-comment {
    margin-left: 40px;
    border-left: 3px solid $border-color;
    background-color: $bg-white;
  }

  // ====================== 标题区域 ======================
  .c-title {
    display: flex;
    align-items: center;
    margin-bottom: 12px;
    padding-bottom: 8px;
    border-bottom: 1px dashed $border-dashed;

    b {
      margin-left: 12px;
      font-weight: 600;
      color: $text-dark;
    }

    em {
      margin: 0 10px;
      color: #dcdfe6;
    }

    time {
      color: $text-gray;
      font-size: 13px;
      margin-left: auto;
    }
  }

  // ====================== 内容区域 ======================
  .c-c {
    line-height: 1.8;
    padding: 8px 12px;
    background-color: $bg-white;
    border-radius: 4px;
    border-left: 3px solid $primary-color;
    margin-bottom: 12px;

    // 高亮提示（如管理员回复）
    &.highlight-tip {
      background-color: #fff7ed;
      border-left-color: #f5883f;
    }
  }

  // ====================== 操作区域（含图标） ======================
  .c-g {
    color: $primary-color;
    cursor: pointer;
    font-size: 14px;
    margin-bottom: 8px;

    span {
      margin-right: 20px;
      transition: all 0.2s ease;
      position: relative;
      padding-right: 10px;
      display: inline-flex; // 图标与文字垂直居中
      align-items: center;

      //  hover 效果（文字 + 图标）
      &:hover {
        color: $hover-color;

        .icon-btn {
          color: $hover-color;
        }
      }

      // 图标按钮
      .icon-btn {
        margin-right: 4px;
        vertical-align: middle;
        cursor: pointer;
      }
    }
  }

  // ====================== 回复表单 ======================
  .reply-form {
    background-color: $bg-white;
    padding: 12px;
    border-radius: 4px;
    margin-bottom: 12px;

    .plbotton {
      text-align: right;
      margin-top: 8px;
    }
  }
}

// ====================== 分页容器 ======================
.pagination-container {
  text-align: center;
  margin-top: 24px;
  margin-bottom: 20px;
}

// ====================== Element UI 样式覆盖（Vue2 需用 /deep/ 穿透） ======================
::v-deep {
  .el-textarea__inner {
    resize: vertical;
    min-height: 60px;
    border-radius: 4px;
    border: 1px solid #dcdfe6;
  }

  .el-button--mini {
    padding: 8px 15px;
    border-radius: 4px;
  }

  .el-pagination {
    .btn-prev,
    .btn-next {
      background-color: #f5f7fa;
    }
  }
}
</style>
